#include <string>
#include "netTools.h"
#ifdef __linux__
#include <arpa/inet.h>
#include <fcntl.h>
#endif



bool setup_socket()
{
#if defined(_WIN32)
    WSADATA wsaData;
    if (WSAStartup(MAKEWORD(2, 2), &wsaData) != 0) {
        return false;
    }
#endif
    return true;
}

bool clean_socket()
{
#if defined(_WIN32)
    if (WSACleanup() != 0) {
        return false;
    }
#endif
    return true;
}

std::string domain2IP(const std::string domain)
{
    struct addrinfo hints = { 0 }, *res = NULL;
    int status = 0;
    char ipstr[INET6_ADDRSTRLEN] = { 0 };

    hints.ai_family = AF_UNSPEC;
    hints.ai_socktype = SOCK_STREAM;

    status = getaddrinfo(domain.c_str(), NULL, &hints, &res);
    if (status != 0) {
        return "";
    }

    void* addr = NULL;
    if  (res->ai_family == AF_INET)
    {
        struct sockaddr_in* ipv4 = (struct sockaddr_in*)res->ai_addr;
        addr = &ipv4->sin_addr;
    }
    else
    {
        struct sockaddr_in6* ipv6 = (struct sockaddr_in6*)res->ai_addr;
        addr = &ipv6->sin6_addr;
    }

    inet_ntop(res->ai_family, addr, ipstr, sizeof(ipstr));

    freeaddrinfo(res);
    return std::string(ipstr);
}

int setSocketNonblocking(TSocket socket)
{
#ifdef _WIN32
    unsigned long mode = 1;
    return ioctlsocket(socket, FIONBIO, &mode);
#elif __linux__
    int flags = fcntl(socket, F_GETFL, 0);
    if (flags == -1) {
        // 处理错误
        return -1;
    }

    if (fcntl(socket, F_SETFL, flags | O_NONBLOCK) == -1) {
        // 处理错误
        return -1;
    }

    return 0; // 成功
#endif

}
